using UnityEditor;
using UnityEngine;
using Devil;

namespace GameToolkit.Editor
{
    [CustomPropertyDrawer(typeof(IDByNameAttribute))]
    public class IDByNameDrawer : PropertyDrawer
    {
        int GetId(Object target, bool locateToPrefab, bool ignoreCase)
        {
            if (target == null)
            {
                return 0;
            }
            else if (locateToPrefab)
            {
                var targetName = GlobalUtil.GetPrefabPath(target);// PrefabUtility.GetPrefabAssetPathOfNearestInstanceRoot(target);
                if (string.IsNullOrEmpty(targetName))
                    return ignoreCase ? target.name.IgnoreCaseToHash() : target.name.ToHash();
                else
                    return ignoreCase ? DevilEditorUtility.GetFileName(targetName).IgnoreCaseToHash() : DevilEditorUtility.GetFileName(targetName).ToHash();
            }
            else
            {
                return ignoreCase ? target.name.IgnoreCaseToHash() : target.name.ToHash();
            }
        }

        public override float GetPropertyHeight(SerializedProperty property, GUIContent label)
        {
            if (property.propertyType != SerializedPropertyType.Integer)
                return 40;
            return base.GetPropertyHeight(property, label);
        }

        public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
        {
            if (property.propertyType != SerializedPropertyType.Integer)
            {
                EditorGUI.HelpBox(position, "NameIDAttribute Only Support Integer Type", MessageType.Warning);
                return;
            }
            var att = attribute as IDByNameAttribute;
            EditorGUI.BeginProperty(position, label, property);
            var lv = EditorGUI.indentLevel;
            var vpos = EditorGUI.PrefixLabel(position, label);
            EditorGUI.indentLevel = 0;
            var w = Mathf.Min(80, vpos.width * 0.4f);
            EditorGUI.BeginDisabledGroup(EditorApplication.isPlayingOrWillChangePlaymode);
            var rect = new Rect(vpos.x, vpos.y, vpos.width - w - 2, vpos.height);
            var id = EditorGUI.IntField(rect, property.intValue);
            rect = new Rect(vpos.xMax - w, vpos.y, w, vpos.height);
            if (GUI.Button(rect, "ID by Name"))
            {
                var ser = property.serializedObject;
                if (ser.isEditingMultipleObjects)
                {
                    var objs = ser.targetObjects;
                    var path = property.propertyPath;
                    for (int i = 0; i < objs.Length; i++)
                    {
                        var _id = GetId(objs[i], att.IsPrefabName, att.IgnoreCase);
                        var target = new SerializedObject(objs[i]);
                        var prop = target.FindProperty(path);
                        if (prop.intValue != _id)
                        {
                            prop.intValue = _id;
                            GUI.changed = true;
                        }
                        target.ApplyModifiedProperties();
                        target.Dispose();
                    }
                }
                else
                {
                    var target = property.serializedObject.targetObject;
                    id = GetId(target, att.IsPrefabName, att.IgnoreCase);
                }
            }
            EditorGUI.EndDisabledGroup();
            if (property.intValue != id)
            {
                property.intValue = id;
                GUI.changed = true;
            }

            EditorGUI.indentLevel = lv;
            EditorGUI.EndProperty();
        }
    }
}